package date0531_1;

import java.util.Arrays;

/**
 * 1、测试 getChars( int , int , char[] , int ) 和 toCharArray()
 * 2、理解使用 + 运算符 直接 连接 两个 字符串 字面量 所执行的操作
 * 3、理解使用 + 运算符 连接 一个 字符串 字面量 和 另一个 String 类型的引用变量 所执行的操作
 * 		  向 面试官 回答时，主要将 Java 8 中的实现过程
 * 4、在 Java 11 中所完成的操作暂时仅做了解
 */

public class StringTestF {

	public static void main(String[] args) {
		
		char[] chars = new char[ 10 ];
		final String s = "黄沙百战穿金甲，不破楼兰终不还" ;
		s.getChars( 8 , 15,  chars , 0 );
		System.out.println( Arrays.toString( chars ) );
		
		char[] array = s.toCharArray();
		System.out.println( Arrays.toString( array ) );
		
		System.out.println( "~ ~ ~ ~ ~ ~ ~ ~ ~ ~ ~ ~ ~ ~ ~ ~" );
		
		String a = "黄沙百战" ; // 1 character strings ( String constant pool )
		String b = "穿金甲" ; // 1 character strings ( String constant pool )
		String c = "黄沙百战穿金甲" ; // 1 character strings ( String constant pool )
		
		// 当使用 + 连接 两个 字符串 直接量时，在 String 常量池中完成 字符串 的 连接操作，
		// 如果 新字符串 在 String常量池 中不存在，则首先将 新字符串 添加到 String 常量池 中并返回该串的地址
		// 如果 新字符串 在 String常量池 中已经存在 则直接返回已经存在的 字符串 的地址 ( 不再添加新拼接的字符串 )
		String d = "黄沙百战" + "穿金甲" ; // 至少在 JDK 11 中已经是在编译阶段就将两个字符串合并了
		System.out.println( c == d ); // true : 使用 == 比较两个变量时是在比较两个变量中存储的值
		System.out.println( System.identityHashCode( c ) );
		System.out.println( System.identityHashCode( d ) );
		
		// 以下 三步 是 Java 8 中的做法
		// 1、StringBuilder sb = new StringBuilder( a ) ; // 创建一个字符缓冲区，并在其中存放  '黄' , '沙' , '百' , '战'
		// 2、sb.append( "穿金甲" ) ; // 在 字符缓冲区 中 追加 '穿' , '金' , '甲' ，此时在 字符缓冲区中存在 7 个字符
		// 3、sb.toString() ; // 在 toString 方法内部创建并返回一个新的 String 实例，其中封装了 "黄沙百战穿金甲"
		String e = a + "穿金甲" ;  //这里有一个new String(value,offset,count)的过程
		// 至少在 JDK 11 中已经是通过 invokedynamic 实现的
		System.out.println( c == e ); // false : 使用 == 比较两个变量时是在比较两个变量中存储的值
		String f = "黄沙百战" + b ;
		System.out.println( c == f ); // false
		
		// StringBuilder sb = new StringBuilder();
		// sb.append( a );
		// sb.append( b );
		// sb.toString();
		String g = a + b ;
		System.out.println( c == g ); // false
		
	}

}
